// vim: set expandtab tabstop=4 shiftwidth=4 fdm=marker:

// Makefile for php.ini reading and global vars using extension function
// Author: terryye<hi@terryye.org>


/* 引入tphp_demofunc的头文件 */
#include "tphp_demofunc.h"

/*初始话ini配置的值 == 2.1引入的内容 ==*/
ZEND_INI_BEGIN()
	//php.ini中配置的数字变量
    ZEND_INI_ENTRY( "mysql.max_persistent", "1", ZEND_INI_ALL, NULL ) 
    ZEND_INI_ENTRY( "variables_order", "GCP", ZEND_INI_ALL, NULL ) //php.ini中配置的字符串变量
	
	//ZEND_INI_ENTRY的
	//第一个参数：
	//	在php.ini文件中用到的名字字符串。为了避免命名空间冲突，尽量使用带有名字空间的配置名 例如tphp_demofunc.myconfig
	//第二个参数:
	//	默认值，而且，不管它是不是数字值，都要使用char*类型的字符串。这主要是依据如下事实：.ini文件中的原值就是文本－
	//	连同其他的一切作为一个文本文件存储。你在后面的脚本中所用到的INI_INT()、INI_FLT()或INI_BOOL()会进行类型转换。
	//第三个参数:
	//	访问模式修饰符。这是个位掩码字段，它决定该INI值在何时和何处是可修改的
	//	常量				值		含义
	//	ZEND_INI_USER		1	配置选项可在用户的 PHP 脚本或 Windows  注册表中设置
	//	ZEND_INI_PERDIR	2	配置选项可在 php.ini, .htaccess 或  httpd.conf 中设置
	//	ZEND_INI_SYSTEM	4	配置选项可在 php.ini or httpd.conf  中设置
	//	ZEND_INI_ALL		7	配置选项可在各处设置
	//第四个参数
	//	忽略第四个参数，只是提一下，它允许在初始设定发生改变时－例如使用ini_set()－触发一个方法回调。这使得当设定改变时，
	//	扩展可以执行更精确的控制(例如把这个ini的值存在一个全局变量中，可以自动更新全局变量的值)，或是根据新的设定触发一个相关的行为。
ZEND_INI_END()

/**
 * 定义本扩展可供外部php函数调用的接口函数列表
 */
zend_function_entry tphp_demofunc_functions[] =
{
	//ZEND_FE使用第一个参数作为PHP函数名，并且在添加了zif前缀后作为C函数名；
	//			 第二个参数用于填充arg_info，用其实现函数参数的类型绑定。通常使用NULL。
    ZEND_FE( tphp_demofunc_sayini, NULL )	//== 2.1引入的内容==
	//ZEND_FE( tphp_demofunc_sayhi, NULL ) //如果你有多个函数，继续在数组里添加。
    {NULL, NULL, NULL} //数组最后一项的成员必须全部为NULL，这用于标记数组的结束。
};

/* 定义本模块的调用信息 */
zend_module_entry tphp_demofunc_module_entry =
{
    STANDARD_MODULE_HEADER,		//PHP标准的模块头部，通常不用修改
    "tphp_demofunc",			//扩展的名称，判断扩展在php中是否已经加载的标识。 使用php -m显示出来的模块名称就是这个字符串
    tphp_demofunc_functions,	//上面定义的本扩展对外提供的函数列表
	//下面的函数我们在tphp_demoini中讲到具体的用途
    ZEND_MINIT(tphp_demofunc),	// php初始化模块时调用的函数。 具体参见PHP程序的执行周期
    ZEND_MSHUTDOWN(tphp_demofunc),	// php结束模块时调用的函数。 具体参见PHP程序的执行周期
    NULL,	// RINIT 
	NULL,	// RSHUTDOWN 
    NULL,	// MINFO 
    "1.0.0", //本扩展的版本号
    STANDARD_MODULE_PROPERTIES  //PHP标准的模块属性，通常不用修改
};

/*
#define ZEND_GET_MODULE(name) \
    BEGIN_EXTERN_C()\
        ZEND_DLEXPORT zend_module_entry *get_module(void) { return &name##_module_entry; }\
    END_EXTERN_C()
因为我们是使用动态库的形式提供扩展，所以需要使用ZEND_GET_MODULE对php留出接口，使其能获取这个模块的相关信息和方法，

如果是内建到php模块内的，非单独的so，无需使用该语句。
*/
ZEND_GET_MODULE( tphp_demofunc )

//根据php.ini的配置有不同表现的函数。
ZEND_FUNCTION(tphp_demofunc_sayini)
{

	char * variables_order = estrdup(INI_STR("variables_order"));
	//注意，需要拷贝从INI_STR()返回的值。这是因为，在进入PHP变量堆栈之前（as far as the PHP variable stack is concerned），它都是个静态字符
	//串。如果你试图修改这个返回的字符串，PHP执行环境会变得不稳定，甚至崩溃。

	long max_persistent = INI_INT("mysql.max_persistent");

	//上面使用了INI_STR获取字符串配置的值。也存在其他类似函数用于取得其他类型的值，长整型、双精度浮点型和
	//布尔型，如下面表格中所示；同时也提供另外的ORIG版本，它们提供在php.ini文件中的INI（的原始）设定（在被.htaccess或ini_set()指令改变之前）
	//获取ini各种类型值的函数
	//INI_STR(name)		INI_ORIG_STR(name)	char * (NULL terminated)
	//INI_INT(name)		INI_ORIG_INT(name)	signed long
	//INI_FLT(name)		INI_ORIG_FLT(name)	signed double
	//INI_BOOL(name)	INI_ORIG_BOOL(name) zend_bool
	zend_printf("variables_order:%s\nmysql.max_persistent:%ld\n", variables_order, max_persistent );
}

//扩展模块初始化时注册ini资源的入口
ZEND_MINIT_FUNCTION( tphp_demofunc )
{
	//#define REGISTER_INI_ENTRIES() zend_register_ini_entries(ini_entries, module_number TSRMLS_CC)
	//调用了 zend_register_ini_entries() 进行了注册，并且强制使用了TSRM的方式。
	REGISTER_INI_ENTRIES();
	return SUCCESS;
}

//扩展模块结束时注销ini资源的入口
ZEND_MSHUTDOWN_FUNCTION( tphp_demofunc )
{
	UNREGISTER_INI_ENTRIES();
	return SUCCESS;
}
